package com.blue.gateway.paycore.alipay.pay;

import com.alibaba.fastjson.JSON;
import com.blue.gateway.annotation.Channel;
import com.blue.gateway.common.Request;
import com.blue.gateway.common.request.PayQueryRequest;
import com.blue.gateway.common.response.PayQueryResponse;
import com.blue.gateway.config.AliConfig;
import com.blue.gateway.config.BaseChannelConfig;
import com.blue.gateway.paycore.alipay.AliMethodEnum;
import com.blue.gateway.paycore.alipay.AliPayConstants;
import com.blue.gateway.dto.Result;
import com.blue.gateway.dto.ResultWrapper;
import com.blue.gateway.enums.PayChannelEnum;
import com.blue.gateway.enums.ResultCodeEnum;
import com.blue.gateway.enums.ServiceChannelEnum;
import com.blue.gateway.utils.DateUtil;
import com.blue.gateway.utils.WebUtil;
import com.blue.gateway.utils.http.HttpClientsUtil;
import com.blue.gateway.utils.sign.AliPaySignature;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;

import java.util.Date;
import java.util.Map;
import java.util.SortedMap;
import java.util.TreeMap;

/**
 * @author xiaoyiming
 * @date 2020/5/4 16:57
 * @depiction https://opendocs.alipay.com/apis/api_1/alipay.trade.query
 */
@Slf4j
@Channel(PayChannel = PayChannelEnum.ALIPAY, ServiceChannel = ServiceChannelEnum.PAY_QUERY)
public class AliPayQueryService extends AliPayService {

    @Override
    public Result validate(Request request) {
        PayQueryRequest payRequest = (PayQueryRequest) request;
        if (StringUtils.isBlank(payRequest.getOutTradeNo())) {
            return ResultWrapper.fail(ResultCodeEnum.PARAM_ILLEGAL);
        }
        if (StringUtils.isBlank(payRequest.getTradeNo())) {
            return ResultWrapper.fail(ResultCodeEnum.PARAM_ILLEGAL);
        }
        return ResultWrapper.success();
    }

    @Override
    public BaseChannelConfig getConfig(Request request) {
        return super.getConfig(request);
    }

    @Override
    public String generateParams(Request request, BaseChannelConfig channelConfig) {
        PayQueryRequest payRequest = (PayQueryRequest) request;
        AliConfig aliConfig = (AliConfig) channelConfig;

        //公共请求参数
        SortedMap<String, String> paramMap = new TreeMap<>();
        paramMap.put("app_id", aliConfig.getAppId());
        paramMap.put("method", AliMethodEnum.TRADE_PAY_QUERY.getMethodName());
        paramMap.put("charset", AliPayConstants.CHARSET_UTF8);
        paramMap.put("sign_type", aliConfig.getSignType());
        paramMap.put("timestamp", DateUtil.formatDateYMDHMS(new Date()));
        paramMap.put("version", AliPayConstants.VERSION);

        //请求参数 biz_content
        SortedMap<String, String> contentMap = new TreeMap<>();
        //订单支付时传入的商户订单号,和支付宝交易号不能同时为空。trade_no,out_trade_no如果同时存在优先取trade_no
        contentMap.put("trade_no", payRequest.getTradeNo());
        contentMap.put("out_trade_no", payRequest.getOutTradeNo());

        paramMap.put("biz_content", JSON.toJSONString(contentMap));

        //参数加密
        String sign = AliPaySignature.sign(paramMap, aliConfig.getPrivateKey());
        paramMap.put("sign", sign);

        return AliPayConstants.GATEWAY_URL + WebUtil.getRequestUrl(paramMap);
    }

    @Override
    public String execute(String requestParams, BaseChannelConfig channelConfig) {
        String result = null;
        try {
            result = HttpClientsUtil.httpClientGet(requestParams);
        } catch (Exception e) {
            // do nothing
        }
        return result;
    }

    /**
     * 查询成功
     * {
     * "alipay_trade_query_response":{
     * "code":"10000",
     * "msg":"Success",
     * "buyer_logon_id":"438***@qq.com",
     * "buyer_pay_amount":"0.00",
     * "buyer_user_id":"2088502959038209",
     * "invoice_amount":"0.00",
     * "out_trade_no":"2789875498798",
     * "point_amount":"0.00",
     * "receipt_amount":"0.00",
     * "send_pay_date":"2020-05-04 19:40:42",
     * "total_amount":"0.01",
     * "trade_no":"2020050422001438201415840865",
     * "trade_status":"TRADE_CLOSED"
     * },
     * "sign":"XrbKYe7MgCCSgAzIztwLoAMlqFP0bL1cV++hWJj7f21mCa0SsEF0mZNQULnKninVo8F05N3iEcqsBkEycXQNVvqRIhsVmDWB9b8BI8LfmsYQdllbeG1D8DEUBdxPDs/pXAQmPkB1n9T7FA6WFGx+ZKnfGV1kSLNCj0fSc2bPh4HYWtiqsfc4L3yj0NoSXXJ7JJf5KMaMDhpHtfX9aoHiAGMApA83TBtEmpNSWd68YlHreYBkgiyQoFVNXpOdxWkP4LKlf9Zl/RxVe3IwtaA3uTDbZjuzDFT4TDw/yKUnaNRL3fzCUr5HnSa+PyVggjvYHf7NkxPGmKZf4AKq6UkLLw=="
     * }
     * <p>
     * 查询失败:
     * {
     * "alipay_trade_query_response":{
     * "code":"40004",
     * "msg":"Business Failed",
     * "sub_code":"ACQ.TRADE_NOT_EXIST",
     * "sub_msg":"交易不存在",
     * "buyer_pay_amount":"0.00",
     * "invoice_amount":"0.00",
     * "out_trade_no":"27898754987981",
     * "point_amount":"0.00",
     * "receipt_amount":"0.00"
     * },
     * "sign":"DIF/OIi6+iQfz+XwAjy6JpaFopdPfh3rxEsQFoEvDUi9T8YA+H8PU6uFm0OyN480SE9e9ctyQYWc8QJQ5hDYErh88sLPWqU7CgfjfLhmceazc117PgTw0b4LV7mGcVCMjBRAt4z8LFkZcFho9IpSwYFqIANkfzqB4z2PevVhecBtGjpNlNYqji4BoO8Vsgl2I3CprFO17In5/abByVZRVNS2EsRbD0ou86t2NJ2jNNdNIpLr3WhJrGv2z6IxhilRMwd4j446pJvMLikeZvg85CFH5K4XOy5skEPodw3GsL+xscNX913EkxkiwNhcAFtf1ogxy9/iHti4rcDuUMVGjQ=="
     * }
     *
     * @param executeResult
     * @return
     */
    @Override
    public Result analysisResult(String executeResult) {
        PayQueryResponse payResponse = new PayQueryResponse();
        Map resultMap = JSON.parseObject(executeResult);
        Map map = JSON.parseObject(String.valueOf(resultMap.get(AliMethodEnum.TRADE_PAY_QUERY.getResponseName())));
        payResponse.setData(executeResult);
        String code = String.valueOf(map.get("code"));
        if (AliPayConstants.SUCCESS_CODE.equals(code)) {
            return ResultWrapper.success(payResponse);
        } else {
            payResponse.setMsg(String.valueOf(map.get("sub_msg")));
            return ResultWrapper.fail(payResponse);
        }
    }
}
